<!DOCTYPE html>
<html lang="en"><head>
    <title>CZH-DEV BLOG</title>
    <meta content="text/html;charset=utf-8" http-equiv="Content-Type">
    <meta content="utf-8" http-equiv="encoding">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta name="format-detection" content="telephone=no" />
    <meta name="theme-color" content="#000084" />
    <link rel="icon" href="https://czh-dev.gitee.io/czh-blog.gitee.io//favicon.ico">
    <link rel="canonical" href="https://czh-dev.gitee.io/czh-blog.gitee.io/">
    
    
</head>
<body>
<nav class="navbar navbar-inverse navbar-fixed-top">
    <div class="navbar-inner">
        <div class="container">
            <button type="button" class="btn btn-navbar" data-toggle="collapse" data-target=".nav-collapse"></button>
            <a class="brand" href="https://czh-dev.gitee.io/czh-blog.gitee.io/">CZH-DEV BLOG</a>
            <div class="nav-collapse collapse">
                <ul class="nav">
                    
                    
                        
                            <li>
                                <a href="/czh-blog.gitee.io/about/">
                                    
                                    <span>About</span>
                                </a>
                            </li>
                        
                    
                        
                            <li>
                                <a href="/czh-blog.gitee.io/post/">
                                    
                                    <span>All posts</span>
                                </a>
                            </li>
                        
                    
                        
                            <li>
                                <a href="/czh-blog.gitee.io/ebook/">
                                    
                                    <span>Resource</span>
                                </a>
                            </li>
                        
                    
                </ul>
            </div>
        </div>
    </div>
</nav><div id="content" class="container">
<div style="display: flex;">
  <div class="row-fluid navmargin">
    <div class="page-header">
      <h1>vi--终端编辑器 - Fri, Feb 10, 2023</h1>
    </div>
    <p class="lead"></p>
    <h1 id="vi--终端中的编辑器"><code>vi</code> —— 终端中的编辑器</h1>
<h2 id="目标">目标</h2>
<ul>
<li><code>vi</code> 简介</li>
<li>打开和新建文件</li>
<li>三种工作模式</li>
<li>常用命令</li>
<li>分屏命令</li>
<li>常用命令速查图</li>
</ul>
<h2 id="01-vi-简介">01. <code>vi</code> 简介</h2>
<h3 id="11-学习-vi-的目的">1.1 学习 <code>vi</code> 的目的</h3>
<ul>
<li>在工作中，要对 <strong>服务器</strong> 上的文件进行 <strong>简单</strong> 的修改，可以使用 <code>ssh</code> 远程登录到服务器上，并且使用 <code>vi</code> 进行快速的编辑即可</li>
<li>常见需要修改的文件包括：
<ul>
<li><strong>源程序</strong></li>
<li><strong>配置文件</strong>，例如 <code>ssh</code> 的配置文件 <code>~/.ssh/config</code></li>
</ul>
</li>
</ul>
<blockquote>
<ul>
<li>在没有图形界面的环境下，要编辑文件，<code>vi</code> 是最佳选择！</li>
<li>每一个要使用 Linux 的程序员，都应该或多或少的学习一些 <code>vi</code> 的常用命令</li>
</ul>
</blockquote>
<h3 id="12-vi-和-vim">1.2 vi 和 vim</h3>
<ul>
<li>在很多 <code>Linux</code> 发行版中，直接把 <code>vi</code> 做成 <code>vim</code> 的软连接</li>
</ul>
<h4 id="vi">vi</h4>
<ul>
<li><code>vi</code> 是 <code>Visual interface</code> 的简称，是 <code>Linux</code> 中 <strong>最经典</strong> 的文本编辑器</li>
<li><code>vi</code> 的核心设计思想 —— <strong>让程序员的手指始终保持在键盘的核心区域，就能完成所有的编辑操作</strong></li>
</ul>
<p><img src="https://czh-pic.oss-cn-guangzhou.aliyuncs.com/202302111204366.png" alt="001_vi键盘-w551"></p>
<ul>
<li><code>vi</code> 的特点：
<ul>
<li><strong>没有图形界面</strong> 的 <strong>功能强大</strong> 的编辑器</li>
<li>只能是编辑 <strong>文本内容</strong>，不能对字体、段落进行排版</li>
<li><strong>不支持鼠标操作</strong></li>
<li><strong>没有菜单</strong></li>
<li><strong>只有命令</strong></li>
</ul>
</li>
<li><code>vi</code> 编辑器在 <strong>系统管理</strong>、<strong>服务器管理</strong> 编辑文件时，<strong>其功能永远不是图形界面的编辑器能比拟的</strong></li>
</ul>
<h4 id="vim"><code>vim</code></h4>
<p><strong>vim = vi improved</strong></p>
<ul>
<li><code>vim</code> 是从 <code>vi</code> 发展出来的一个文本编辑器，支持 <strong>代码补全</strong>、<strong>编译</strong> 及 <strong>错误跳转</strong> 等方便编程的功能特别丰富，在程序员中被广泛使用，被称为 <strong>编辑器之神</strong></li>
</ul>
<h4 id="查询软连接命令知道">查询软连接命令（知道）</h4>
<ul>
<li>在很多 <code>Linux</code> 发行版中直接把 <code>vi</code> 做成 <code>vim</code> 的软连接</li>
</ul>
<div class="highlight"><pre tabindex="0" style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;"><code class="language-bash" data-lang="bash"><span style="display:flex;"><span><span style="color:#75715e"># 查找 vi 的运行文件</span>
</span></span><span style="display:flex;"><span>
</span></span><span style="display:flex;"><span>$ which vi
</span></span><span style="display:flex;"><span>$ ls -l /usr/bin/vi
</span></span><span style="display:flex;"><span>$ ls -l /etc/alternatives/vi
</span></span><span style="display:flex;"><span>$ ls -l /usr/bin/vim.basic
</span></span><span style="display:flex;"><span>
</span></span><span style="display:flex;"><span><span style="color:#75715e"># 查找 vim 的运行文件</span>
</span></span><span style="display:flex;"><span>$ which vim
</span></span><span style="display:flex;"><span>$ ls -l /usr/bin/vim
</span></span><span style="display:flex;"><span>$ ls -l /etc/alternatives/vim
</span></span><span style="display:flex;"><span>$ ls -l /usr/bin/vim.basic 
</span></span></code></pre></div><h2 id="02-打开和新建文件">02. 打开和新建文件</h2>
<ul>
<li>在终端中输入 <code>vi</code> <strong>在后面跟上文件名</strong> 即可</li>
</ul>
<div class="highlight"><pre tabindex="0" style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;"><code class="language-bash" data-lang="bash"><span style="display:flex;"><span>$ vi 文件名
</span></span></code></pre></div><ul>
<li>如果文件已经存在，会直接打开该文件</li>
<li>如果文件不存在，会新建一个文件</li>
</ul>
<h3 id="21-打开文件并且定位行">2.1 打开文件并且定位行</h3>
<ul>
<li>
<p>在日常工作中，有可能会遇到 <strong>打开一个文件，并定位到指定行</strong> 的情况</p>
</li>
<li>
<p>例如：在开发时，<strong>知道某一行代码有错误</strong>，可以 <strong>快速定位</strong> 到出错代码的位置</p>
</li>
<li>
<p>这个时候，可以使用以下命令打开文件</p>
</li>
</ul>
<div class="highlight"><pre tabindex="0" style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;"><code class="language-bash" data-lang="bash"><span style="display:flex;"><span>$ vi 文件名 +行数
</span></span></code></pre></div><blockquote>
<p>提示：如果只带上 <code>+</code> 而不指定行号，会直接定位到文件末尾</p>
</blockquote>
<h3 id="22-异常处理">2.2 异常处理</h3>
<ul>
<li>如果 <code>vi</code> 异常退出，在磁盘上可能会保存有 <strong>交换文件</strong></li>
<li>下次再使用 <code>vi</code> 编辑该文件时，会看到以下屏幕信息，按下字母 <code>d</code> 可以 <strong>删除交换文件</strong> 即可</li>
</ul>
<blockquote>
<p>提示：按下键盘时，注意关闭输入法</p>
</blockquote>
<p><img src="https://czh-pic.oss-cn-guangzhou.aliyuncs.com/202302111205509.png" alt="002_删除交换文件-w1048"></p>
<h2 id="03-三种工作模式">03. 三种工作模式</h2>
<ul>
<li>
<p><code>vi</code> 有三种基本工作模式：</p>
<ol>
<li><strong>命令模式</strong>
<ul>
<li><strong>打开文件首先进入命令模式</strong>，是使用 <code>vi</code> 的 <strong>入口</strong></li>
<li>通过 <strong>命令</strong> 对文件进行常规的编辑操作，例如：<strong>定位</strong>、<strong>翻页</strong>、<strong>复制</strong>、<strong>粘贴</strong>、<strong>删除</strong>……</li>
<li>在其他图形编辑器下，通过 <strong>快捷键</strong> 或者 <strong>鼠标</strong> 实现的操作，都在 <strong>命令模式</strong> 下实现</li>
</ul>
</li>
<li><strong>末行模式</strong> —— 执行 <strong>保存</strong>、<strong>退出</strong> 等操作
<ul>
<li>要退出 <code>vi</code> 返回到控制台，需要在末行模式下输入命令</li>
<li><strong>末行模式</strong> 是 <code>vi</code> 的 <strong>出口</strong></li>
</ul>
</li>
<li><strong>编辑模式</strong> —— 正常的编辑文字</li>
</ol>
</li>
</ul>
<p><img src="https://czh-pic.oss-cn-guangzhou.aliyuncs.com/202302111205217.png" alt="003_vi的模式-w500"></p>
<blockquote>
<p>提示：在 <code>Touch Bar</code> 的 Mac 电脑上 ，按 <code>ESC</code> 不方便，可以使用 <code>CTRL + [</code> 替代</p>
</blockquote>
<h3 id="末行模式命令">末行模式命令</h3>
<table>
<thead>
<tr>
<th style="text-align:center">命令</th>
<th style="text-align:center">英文</th>
<th>功能</th>
</tr>
</thead>
<tbody>
<tr>
<td style="text-align:center">w</td>
<td style="text-align:center">write</td>
<td>保存</td>
</tr>
<tr>
<td style="text-align:center">q</td>
<td style="text-align:center">quit</td>
<td>退出，如果没有保存，不允许退出</td>
</tr>
<tr>
<td style="text-align:center">q!</td>
<td style="text-align:center">quit</td>
<td>强行退出，不保存退出</td>
</tr>
<tr>
<td style="text-align:center">wq</td>
<td style="text-align:center">write &amp; quit</td>
<td>保存并退出</td>
</tr>
<tr>
<td style="text-align:center">x</td>
<td style="text-align:center"></td>
<td>保存并退出</td>
</tr>
</tbody>
</table>
<h2 id="04-常用命令">04. 常用命令</h2>
<h3 id="命令线路图">命令线路图</h3>
<ol start="0">
<li>重复次数
<ul>
<li>在命令模式下，<strong>先输入一个数字</strong>，<strong>再跟上一个命令</strong>，可以让该命令 <strong>重复执行指定次数</strong></li>
</ul>
</li>
<li>移动和选择（<strong>多练</strong>）
<ul>
<li><code>vi</code> 之所以快，关键在于 <strong>能够快速定位到要编辑的代码行</strong></li>
<li><strong>移动命令</strong> 能够 和 <strong>编辑操作</strong> 命令 <strong>组合使用</strong></li>
</ul>
</li>
<li>编辑操作
<ul>
<li><strong>删除</strong>、<strong>复制</strong>、<strong>粘贴</strong>、<strong>替换</strong>、<strong>缩排</strong></li>
</ul>
</li>
<li>撤销和重复</li>
<li>查找替换</li>
<li>编辑</li>
</ol>
<h4 id="学习提示">学习提示</h4>
<ol>
<li><code>vi</code> 的命令较多，<strong>不要期望一下子全部记住</strong>，个别命令忘记了，只是会影响编辑速度而已</li>
<li>在使用 <code>vi</code> 命令时，注意 <strong>关闭中文输入法</strong></li>
</ol>
<h3 id="41-移动基本">4.1 移动（基本）</h3>
<ul>
<li>要熟练使用 <code>vi</code>，首先应该学会怎么在 <strong>命令模式</strong> 下样快速移动光标</li>
<li><strong>编辑操作命令</strong>，能够和 <strong>移动命令</strong> 结合在一起使用</li>
</ul>
<h4 id="1-上下左右">1) 上、下、左、右</h4>
<table>
<thead>
<tr>
<th style="text-align:center">命令</th>
<th>功能</th>
<th style="text-align:center">手指</th>
</tr>
</thead>
<tbody>
<tr>
<td style="text-align:center">h</td>
<td>向左</td>
<td style="text-align:center">食指</td>
</tr>
<tr>
<td style="text-align:center">j</td>
<td>向下</td>
<td style="text-align:center">食指</td>
</tr>
<tr>
<td style="text-align:center">k</td>
<td>向上</td>
<td style="text-align:center">中指</td>
</tr>
<tr>
<td style="text-align:center">l</td>
<td>向右</td>
<td style="text-align:center">无名指</td>
</tr>
</tbody>
</table>
<p><img src="https://czh-pic.oss-cn-guangzhou.aliyuncs.com/202302111205928.png" alt="005_移动光标-w551"></p>
<h4 id="2-行内移动">2) 行内移动</h4>
<table>
<thead>
<tr>
<th style="text-align:center">命令</th>
<th style="text-align:center">英文</th>
<th>功能</th>
</tr>
</thead>
<tbody>
<tr>
<td style="text-align:center">w</td>
<td style="text-align:center">word</td>
<td>向后移动一个单词</td>
</tr>
<tr>
<td style="text-align:center">b</td>
<td style="text-align:center">back</td>
<td>向前移动一个单词</td>
</tr>
<tr>
<td style="text-align:center">0</td>
<td style="text-align:center"></td>
<td>行首</td>
</tr>
<tr>
<td style="text-align:center">^</td>
<td style="text-align:center"></td>
<td>行首，第一个不是空白字符的位置</td>
</tr>
<tr>
<td style="text-align:center">$</td>
<td style="text-align:center"></td>
<td>行尾</td>
</tr>
</tbody>
</table>
<h4 id="3-行数移动">3) 行数移动</h4>
<table>
<thead>
<tr>
<th style="text-align:center">命令</th>
<th style="text-align:center">英文</th>
<th>功能</th>
</tr>
</thead>
<tbody>
<tr>
<td style="text-align:center">gg</td>
<td style="text-align:center">go</td>
<td>文件顶部</td>
</tr>
<tr>
<td style="text-align:center">G</td>
<td style="text-align:center">go</td>
<td>文件末尾</td>
</tr>
<tr>
<td style="text-align:center">数字gg</td>
<td style="text-align:center">go</td>
<td>移动到 数字 对应行数</td>
</tr>
<tr>
<td style="text-align:center">数字G</td>
<td style="text-align:center">go</td>
<td>移动到 数字 对应行数</td>
</tr>
<tr>
<td style="text-align:center">:数字</td>
<td style="text-align:center"></td>
<td>移动到 数字 对应行数</td>
</tr>
</tbody>
</table>
<h4 id="4-屏幕移动">4) 屏幕移动</h4>
<table>
<thead>
<tr>
<th style="text-align:center">命令</th>
<th style="text-align:center">英文</th>
<th>功能</th>
</tr>
</thead>
<tbody>
<tr>
<td style="text-align:center">Ctrl + b</td>
<td style="text-align:center">back</td>
<td>向上翻页</td>
</tr>
<tr>
<td style="text-align:center">Ctrl + f</td>
<td style="text-align:center">forward</td>
<td>向下翻页</td>
</tr>
<tr>
<td style="text-align:center">H</td>
<td style="text-align:center">Head</td>
<td>屏幕顶部</td>
</tr>
<tr>
<td style="text-align:center">M</td>
<td style="text-align:center">Middle</td>
<td>屏幕中间</td>
</tr>
<tr>
<td style="text-align:center">L</td>
<td style="text-align:center">Low</td>
<td>屏幕底部</td>
</tr>
</tbody>
</table>
<h3 id="42-移动程序">4.2 移动（程序）</h3>
<h4 id="1-段落移动">1) 段落移动</h4>
<ul>
<li><code>vi</code> 中使用 空行 来区分段落</li>
<li>在程序开发时，通常 <strong>一段功能相关的代码会写在一起</strong> —— 之间没有空行</li>
</ul>
<table>
<thead>
<tr>
<th style="text-align:center">命令</th>
<th>功能</th>
</tr>
</thead>
<tbody>
<tr>
<td style="text-align:center">{</td>
<td>上一段</td>
</tr>
<tr>
<td style="text-align:center">}</td>
<td>下一段</td>
</tr>
</tbody>
</table>
<h4 id="2-括号切换">2) 括号切换</h4>
<ul>
<li>在程序世界中，<code>()</code>、<code>[]</code>、<code>{}</code> 使用频率很高，而且 <strong>都是成对出现的</strong></li>
</ul>
<table>
<thead>
<tr>
<th style="text-align:center">命令</th>
<th>功能</th>
</tr>
</thead>
<tbody>
<tr>
<td style="text-align:center">%</td>
<td>括号匹配及切换</td>
</tr>
</tbody>
</table>
<h4 id="3-标记">3) 标记</h4>
<ul>
<li>在开发时，某一块代码可能<strong>需要稍后处理</strong>，例如：编辑、查看</li>
<li>此时先使用 <code>m</code> 增加一个标记，这样可以 <strong>在需要时快速地跳转回来</strong> 或者 <strong>执行其他编辑操作</strong></li>
<li><strong>标记名称</strong> 可以是 <code>a~z</code> 或者 <code>A~Z</code> 之间的任意 <strong>一个</strong> 字母</li>
<li>添加了标记的 <strong>行如果被删除</strong>，<strong>标记同时被删除</strong></li>
<li>如果 <strong>在其他行添加了相同名称的标记</strong>，<strong>之前添加的标记也会被替换掉</strong></li>
</ul>
<table>
<thead>
<tr>
<th style="text-align:center">命令</th>
<th style="text-align:center">英文</th>
<th>功能</th>
</tr>
</thead>
<tbody>
<tr>
<td style="text-align:center">mx</td>
<td style="text-align:center">mark</td>
<td>添加标记 x，x 是 a~z 或者 A~Z 之间的任意一个字母</td>
</tr>
<tr>
<td style="text-align:center">&lsquo;x</td>
<td style="text-align:center"></td>
<td>直接定位到标记 x 所在位置</td>
</tr>
</tbody>
</table>
<h3 id="43-选中文本可视模式">4.3 选中文本（可视模式）</h3>
<ul>
<li>学习 <code>复制</code> 命令前，应该先学会 <strong>怎么样选中 要复制的代码</strong></li>
<li>在 <code>vi</code> 中要选择文本，需要先使用 <code>Visual</code> 命令切换到 <strong>可视模式</strong></li>
<li><code>vi</code> 中提供了 <strong>三种</strong> 可视模式，可以方便程序员选择 <strong>选中文本的方式</strong></li>
<li>按 <code>ESC</code> 可以放弃选中，返回到 <strong>命令模式</strong></li>
</ul>
<table>
<thead>
<tr>
<th style="text-align:center">命令</th>
<th>模式</th>
<th>功能</th>
</tr>
</thead>
<tbody>
<tr>
<td style="text-align:center">v</td>
<td>可视模式</td>
<td>从光标位置开始按照正常模式选择文本</td>
</tr>
<tr>
<td style="text-align:center">V</td>
<td>可视行模式</td>
<td>选中光标经过的完整行</td>
</tr>
<tr>
<td style="text-align:center">Ctrl + v</td>
<td>可视块模式</td>
<td>垂直方向选中文本</td>
</tr>
</tbody>
</table>
<ul>
<li><strong>可视模式</strong>下，可以和 <strong>移动命令</strong> 连用，例如：<code>ggVG</code> 能够选中所有内容</li>
</ul>
<h3 id="44-撤销和恢复撤销">4.4 撤销和恢复撤销</h3>
<ul>
<li>在学习编辑命令之前，先要知道怎样撤销之前一次 <strong>错误的</strong> 编辑动作！</li>
</ul>
<table>
<thead>
<tr>
<th style="text-align:center">命令</th>
<th style="text-align:center">英文</th>
<th>功能</th>
</tr>
</thead>
<tbody>
<tr>
<td style="text-align:center">u</td>
<td style="text-align:center">undo</td>
<td>撤销上次命令</td>
</tr>
<tr>
<td style="text-align:center">CTRL + r</td>
<td style="text-align:center">redo</td>
<td>恢复撤销的命令</td>
</tr>
</tbody>
</table>
<h3 id="45-删除文本">4.5 删除文本</h3>
<table>
<thead>
<tr>
<th style="text-align:center">命令</th>
<th style="text-align:center">英文</th>
<th>功能</th>
</tr>
</thead>
<tbody>
<tr>
<td style="text-align:center">x</td>
<td style="text-align:center">cut</td>
<td>删除光标所在字符，或者选中文字</td>
</tr>
<tr>
<td style="text-align:center">d(移动命令)</td>
<td style="text-align:center">delete</td>
<td>删除移动命令对应的内容</td>
</tr>
<tr>
<td style="text-align:center">dd</td>
<td style="text-align:center">delete</td>
<td>删除光标所在行，可以 ndd 复制多行</td>
</tr>
<tr>
<td style="text-align:center">D</td>
<td style="text-align:center">delete</td>
<td>删除至行尾</td>
</tr>
</tbody>
</table>
<blockquote>
<p>提示：如果使用 <strong>可视模式</strong> 已经选中了一段文本，那么无论使用 <code>d</code> 还是 <code>x</code>，都可以删除选中文本</p>
</blockquote>
<ul>
<li>删除命令可以和 <strong>移动命令</strong> 连用，以下是常见的组合命令：</li>
</ul>
<pre tabindex="0"><code>* dw        # 从光标位置删除到单词末尾
* d0        # 从光标位置删除到一行的起始位置
* d}        # 从光标位置删除到段落结尾
* ndd       # 从光标位置向下连续删除 n 行
* d代码行G   # 从光标所在行 删除到 指定代码行 之间的所有代码
* d&#39;a       # 从光标所在行 删除到 标记a 之间的所有代码
</code></pre><h3 id="46-复制粘贴">4.6 复制、粘贴</h3>
<ul>
<li><code>vi</code> 中提供有一个 <strong>被复制文本的缓冲区</strong>
<ul>
<li><strong>复制</strong> 命令会将选中的文字保存在缓冲区</li>
<li><strong>删除</strong> 命令删除的文字会被保存在缓冲区</li>
<li>在需要的位置，使用 <strong>粘贴</strong> 命令可以将缓冲区的文字插入到光标所在位置</li>
</ul>
</li>
</ul>
<table>
<thead>
<tr>
<th style="text-align:center">命令</th>
<th style="text-align:center">英文</th>
<th>功能</th>
</tr>
</thead>
<tbody>
<tr>
<td style="text-align:center">y(移动命令)</td>
<td style="text-align:center">copy</td>
<td>复制</td>
</tr>
<tr>
<td style="text-align:center">yy</td>
<td style="text-align:center">copy</td>
<td>复制一行，可以 nyy 复制多行</td>
</tr>
<tr>
<td style="text-align:center">p</td>
<td style="text-align:center">paste</td>
<td>粘贴</td>
</tr>
</tbody>
</table>
<p><strong>提示</strong></p>
<ul>
<li>命令 <code>d</code>、<code>x</code> 类似于图形界面的 <strong>剪切操作</strong> —— <code>CTRL + X</code></li>
<li>命令 <code>y</code> 类似于图形界面的 <strong>复制操作</strong> —— <code>CTRL + C</code></li>
<li>命令 <code>p</code> 类似于图形界面的 <strong>粘贴操作</strong> —— <code>CTRL + V</code></li>
<li><code>vi</code> 中的 <strong>文本缓冲区同样只有一个</strong>，如果后续做过 <strong>复制、剪切</strong> 操作，之前缓冲区中的内容会被替换</li>
</ul>
<p><strong>注意</strong></p>
<ul>
<li><code>vi</code> 中的 <strong>文本缓冲区</strong> 和系统的 <strong>剪贴板</strong> 不是同一个</li>
<li>所以在其他软件中使用 <code>CTRL + C</code> 复制的内容，不能在 <code>vi</code> 中通过 <code>P</code> 命令粘贴</li>
<li>可以在 <strong>编辑模式</strong> 下使用 <strong>鼠标右键粘贴</strong></li>
</ul>
<h3 id="47-替换">4.7 替换</h3>
<table>
<thead>
<tr>
<th style="text-align:center">命令</th>
<th style="text-align:center">英文</th>
<th>功能</th>
<th>工作模式</th>
</tr>
</thead>
<tbody>
<tr>
<td style="text-align:center">r</td>
<td style="text-align:center">replace</td>
<td>替换当前字符</td>
<td>命令模式</td>
</tr>
<tr>
<td style="text-align:center">R</td>
<td style="text-align:center">replace</td>
<td>替换当前行光标后的字符</td>
<td>替换模式</td>
</tr>
</tbody>
</table>
<ul>
<li><code>R</code> 命令可以进入 <strong>替换模式</strong>，替换完成后，按下 <code>ESC</code> 可以回到 <strong>命令模式</strong></li>
<li><strong>替换命令</strong> 的作用就是不用进入 <strong>编辑模式</strong>，对文件进行 <strong>轻量级的修改</strong></li>
</ul>
<h3 id="48-缩排和重复执行">4.8 缩排和重复执行</h3>
<table>
<thead>
<tr>
<th style="text-align:center">命令</th>
<th>功能</th>
</tr>
</thead>
<tbody>
<tr>
<td style="text-align:center">&raquo;</td>
<td>向右增加缩进</td>
</tr>
<tr>
<td style="text-align:center">&laquo;</td>
<td>向左减少缩进</td>
</tr>
<tr>
<td style="text-align:center">.</td>
<td>重复上次命令</td>
</tr>
</tbody>
</table>
<ul>
<li><strong>缩排命令</strong> 在开发程序时，<strong>统一增加代码的缩进</strong> 比较有用！
<ul>
<li>一次性 <strong>在选中代码前增加 4 个空格</strong>，就叫做 <strong>增加缩进</strong></li>
<li>一次性 <strong>在选中代码前删除 4 个空格</strong>，就叫做 <strong>减少缩进</strong></li>
</ul>
</li>
<li>在 <strong>可视模式</strong> 下，缩排命令只需要使用 <strong>一个</strong> <code>&gt;</code> 或者 <code>&lt;</code></li>
</ul>
<blockquote>
<p>在程序中，<strong>缩进</strong> 通常用来表示代码的归属关系</p>
<ul>
<li>前面空格越少，代码的级别越高</li>
<li>前面空格越多，代码的级别越低</li>
</ul>
</blockquote>
<h3 id="49-查找">4.9 查找</h3>
<h4 id="常规查找">常规查找</h4>
<table>
<thead>
<tr>
<th style="text-align:center">命令</th>
<th>功能</th>
</tr>
</thead>
<tbody>
<tr>
<td style="text-align:center">/str</td>
<td>查找 str</td>
</tr>
</tbody>
</table>
<ul>
<li>查找到指定内容之后，使用 <code>Next</code> 查找下一个出现的位置：
<ul>
<li><code>n</code>: 查找下一个</li>
<li><code>N</code>: 查找上一个</li>
</ul>
</li>
<li>如果不想看到高亮显示，可以随便查找一个文件中不存在的内容即可</li>
</ul>
<h4 id="单词快速匹配">单词快速匹配</h4>
<table>
<thead>
<tr>
<th style="text-align:center">命令</th>
<th>功能</th>
</tr>
</thead>
<tbody>
<tr>
<td style="text-align:center">*</td>
<td>向后查找当前光标所在单词</td>
</tr>
<tr>
<td style="text-align:center">#</td>
<td>向前查找当前光标所在单词</td>
</tr>
</tbody>
</table>
<ul>
<li>在开发中，通过单词快速匹配，可以快速看到这个单词在其他什么位置使用过</li>
</ul>
<h3 id="410-查找并替换">4.10 查找并替换</h3>
<ul>
<li>在 <code>vi</code> 中查找和替换命令需要在 <strong>末行模式</strong> 下执行</li>
<li>记忆命令格式：</li>
</ul>
<pre tabindex="0"><code>:%s///g
</code></pre><h4 id="1-全局替换">1) 全局替换</h4>
<ul>
<li><strong>一次性</strong>替换文件中的 <strong>所有出现的旧文本</strong></li>
<li>命令格式如下：</li>
</ul>
<pre tabindex="0"><code>:%s/旧文本/新文本/g
</code></pre><h4 id="2-可视区域替换">2) 可视区域替换</h4>
<ul>
<li><strong>先选中</strong> 要替换文字的 <strong>范围</strong></li>
<li>命令格式如下：</li>
</ul>
<pre tabindex="0"><code>:s/旧文本/新文本/g
</code></pre><h4 id="3-确认替换">3) 确认替换</h4>
<ul>
<li>如果把末尾的 <code>g</code> 改成 <code>gc</code> 在替换的时候，会有提示！<strong>推荐使用！</strong></li>
</ul>
<pre tabindex="0"><code>:%s/旧文本/新文本/gc
</code></pre><ol>
<li><code>y</code> - <code>yes</code> 替换</li>
<li><code>n</code> - <code>no</code> 不替换</li>
<li><code>a</code> - <code>all</code> 替换所有</li>
<li><code>q</code> - <code>quit</code> 退出替换</li>
<li><code>l</code> - <code>last</code> 最后一个，并把光标移动到行首</li>
<li><code>^E</code> 向下滚屏</li>
<li><code>^Y</code> 向上滚屏</li>
</ol>
<h3 id="411-插入命令">4.11 插入命令</h3>
<ul>
<li>在 <code>vi</code> 中除了常用的 <code>i</code> 进入 <strong>编辑模式</strong> 外，还提供了以下命令同样可以进入编辑模式：</li>
</ul>
<table>
<thead>
<tr>
<th style="text-align:center">命令</th>
<th style="text-align:center">英文</th>
<th>功能</th>
<th style="text-align:center">常用</th>
</tr>
</thead>
<tbody>
<tr>
<td style="text-align:center">i</td>
<td style="text-align:center">insert</td>
<td>在当前字符前插入文本</td>
<td style="text-align:center">常用</td>
</tr>
<tr>
<td style="text-align:center">I</td>
<td style="text-align:center">insert</td>
<td>在行首插入文本</td>
<td style="text-align:center">较常用</td>
</tr>
<tr>
<td style="text-align:center">a</td>
<td style="text-align:center">append</td>
<td>在当前字符后添加文本</td>
<td style="text-align:center"></td>
</tr>
<tr>
<td style="text-align:center">A</td>
<td style="text-align:center">append</td>
<td>在行末添加文本</td>
<td style="text-align:center">较常用</td>
</tr>
<tr>
<td style="text-align:center">o</td>
<td style="text-align:center"></td>
<td>在当前行后面插入一空行</td>
<td style="text-align:center">常用</td>
</tr>
<tr>
<td style="text-align:center">O</td>
<td style="text-align:center"></td>
<td>在当前行前面插入一空行</td>
<td style="text-align:center">常用</td>
</tr>
</tbody>
</table>
<p><img src="https://czh-pic.oss-cn-guangzhou.aliyuncs.com/202302111205026.png" alt="004_插入命令-w400"></p>
<h4 id="演练-1--编辑命令和数字连用">演练 1 —— 编辑命令和数字连用</h4>
<ul>
<li>在开发中，可能会遇到连续输入 <code>N</code> 个同样的字符</li>
</ul>
<blockquote>
<p>在 <code>Python</code> 中有简单的方法，但是其他语言中通常需要自己输入</p>
</blockquote>
<ul>
<li>例如：<code>**********</code> 连续 10 个星号</li>
</ul>
<p>要实现这个效果可以在 <strong>命令模式</strong> 下</p>
<ol>
<li>输入 <code>10</code>，表示要重复 10 次</li>
<li>输入 <code>i</code> 进入 <strong>编辑模式</strong></li>
<li>输入 <code>*</code> 也就是重复的文字</li>
<li>按下 <code>ESC</code> 返回到 <strong>命令模式</strong>，返回之后 <code>vi</code> 就会把第 <code>2、3</code> 两步的操作重复 <code>10</code> 次</li>
</ol>
<blockquote>
<p>提示：正常开发时，在 <strong>进入编辑模式之前，不要按数字</strong></p>
</blockquote>
<h4 id="演练-2--利用-可视块-给多行代码增加注释">演练 2 —— 利用 可视块 给多行代码增加注释</h4>
<ul>
<li>在开发中，可能会遇到一次性给多行代码 <strong>增加注释</strong> 的情况</li>
</ul>
<blockquote>
<p>在 <code>Python</code> 中，要给代码增加注释，可以在代码前增加一个 <code># </code></p>
</blockquote>
<p>要实现这个效果可以在 <strong>命令模式</strong> 下</p>
<ol>
<li>移动到要添加注释的 <strong>第 1 行代码</strong>，按 <code>^</code> 来到行首</li>
<li>按 <code>CTRL + v</code> 进入 <strong>可视块</strong> 模式</li>
<li>使用 <code>j</code> 向下连续选中要添加的代码行</li>
<li>输入 <code>I</code> 进入 <strong>编辑模式</strong>，并在 <strong>行首插入</strong>，注意：一定要使用 <strong>I</strong></li>
<li>输入 <code># </code> 也就是注释符号</li>
<li>按下 <code>ESC</code> 返回到 <strong>命令模式</strong>，返回之后 <code>vi</code> 会在之前选中的每一行代码 <strong>前</strong> 插入 <code># </code></li>
</ol>
<h2 id="05-分屏命令">05. 分屏命令</h2>
<ul>
<li>属于 <code>vi</code> 的高级命令 —— 可以 <strong>同时编辑和查看多个文件</strong></li>
</ul>
<h3 id="51-末行命令扩展">5.1 末行命令扩展</h3>
<p><strong>末行命令</strong> 主要是针对文件进行操作的：<strong>保存</strong>、<strong>退出</strong>、<strong>保存&amp;退出</strong>、<strong>搜索&amp;替换</strong>、<strong>另存</strong>、<strong>新建</strong>、<strong>浏览文件</strong></p>
<table>
<thead>
<tr>
<th style="text-align:center">命令</th>
<th style="text-align:center">英文</th>
<th>功能</th>
</tr>
</thead>
<tbody>
<tr>
<td style="text-align:center">:e .</td>
<td style="text-align:center">edit</td>
<td>会打开内置的文件浏览器，浏览要当前目录下的文件</td>
</tr>
<tr>
<td style="text-align:center">:n 文件名</td>
<td style="text-align:center">new</td>
<td>新建文件</td>
</tr>
<tr>
<td style="text-align:center">:w 文件名</td>
<td style="text-align:center">write</td>
<td>另存为，但是仍然编辑当前文件，并不会切换文件</td>
</tr>
</tbody>
</table>
<blockquote>
<p>提示：切换文件之前，必须保证当前这个文件已经被保存！</p>
</blockquote>
<ul>
<li>已经学习过的 <strong>末行命令</strong>：</li>
</ul>
<table>
<thead>
<tr>
<th style="text-align:center">命令</th>
<th style="text-align:center">英文</th>
<th>功能</th>
</tr>
</thead>
<tbody>
<tr>
<td style="text-align:center">:w</td>
<td style="text-align:center">write</td>
<td>保存</td>
</tr>
<tr>
<td style="text-align:center">:q</td>
<td style="text-align:center">quit</td>
<td>退出，如果没有保存，不允许退出</td>
</tr>
<tr>
<td style="text-align:center">:q!</td>
<td style="text-align:center">quit</td>
<td>强行退出，不保存退出</td>
</tr>
<tr>
<td style="text-align:center">:wq</td>
<td style="text-align:center">write &amp; quit</td>
<td>保存并退出</td>
</tr>
<tr>
<td style="text-align:center">:x</td>
<td style="text-align:center"></td>
<td>保存并退出</td>
</tr>
<tr>
<td style="text-align:center">:%s///gc</td>
<td style="text-align:center"></td>
<td>确认搜索并替换</td>
</tr>
</tbody>
</table>
<blockquote>
<p>在实际开发中，可以使用 <code>w</code> 命令 <strong>阶段性的备份代码</strong></p>
</blockquote>
<h3 id="52-分屏命令">5.2 分屏命令</h3>
<ul>
<li>使用 <strong>分屏命令</strong>，可以 <strong>同时编辑和查看多个文件</strong></li>
</ul>
<table>
<thead>
<tr>
<th style="text-align:center">命令</th>
<th style="text-align:center">英文</th>
<th>功能</th>
</tr>
</thead>
<tbody>
<tr>
<td style="text-align:center">:sp [文件名]</td>
<td style="text-align:center">split</td>
<td>横向增加分屏</td>
</tr>
<tr>
<td style="text-align:center">:vsp [文件名]</td>
<td style="text-align:center">vertical split</td>
<td>纵向增加分屏</td>
</tr>
</tbody>
</table>
<h4 id="1-切换分屏窗口">1) 切换分屏窗口</h4>
<blockquote>
<p>分屏窗口都是基于 <code>CTRL + W</code> 这个快捷键的，<code>w</code> 对应的英文单词是 <code>window</code></p>
</blockquote>
<table>
<thead>
<tr>
<th style="text-align:center">命令</th>
<th style="text-align:center">英文</th>
<th>功能</th>
</tr>
</thead>
<tbody>
<tr>
<td style="text-align:center">w</td>
<td style="text-align:center">window</td>
<td>切换到下一个窗口</td>
</tr>
<tr>
<td style="text-align:center">r</td>
<td style="text-align:center">reverse</td>
<td>互换窗口</td>
</tr>
<tr>
<td style="text-align:center">c</td>
<td style="text-align:center">close</td>
<td>关闭当前窗口，但是不能关闭最后一个窗口</td>
</tr>
<tr>
<td style="text-align:center">q</td>
<td style="text-align:center">quit</td>
<td>退出当前窗口，如果是最后一个窗口，则关闭 vi</td>
</tr>
<tr>
<td style="text-align:center">o</td>
<td style="text-align:center">other</td>
<td>关闭其他窗口</td>
</tr>
</tbody>
</table>
<h4 id="2-调整窗口大小">2) 调整窗口大小</h4>
<blockquote>
<p>分屏窗口都是基于 <code>CTRL + W</code> 这个快捷键的，<code>w</code> 对应的英文单词是 <code>window</code></p>
</blockquote>
<table>
<thead>
<tr>
<th style="text-align:center">命令</th>
<th style="text-align:center">英文</th>
<th>功能</th>
</tr>
</thead>
<tbody>
<tr>
<td style="text-align:center">+</td>
<td style="text-align:center"></td>
<td>增加窗口高度</td>
</tr>
<tr>
<td style="text-align:center">-</td>
<td style="text-align:center"></td>
<td>减少窗口高度</td>
</tr>
<tr>
<td style="text-align:center">&gt;</td>
<td style="text-align:center"></td>
<td>增加窗口宽度</td>
</tr>
<tr>
<td style="text-align:center">&lt;</td>
<td style="text-align:center"></td>
<td>减少窗口宽度</td>
</tr>
<tr>
<td style="text-align:center">=</td>
<td style="text-align:center"></td>
<td>等分窗口大小</td>
</tr>
</tbody>
</table>
<blockquote>
<p>调整窗口宽高的命令可以和数字连用，例如：<code>5 CTRL + W +</code> 连续 5 次增加高度</p>
</blockquote>
<h2 id="06-常用命令速查图">06. 常用命令速查图</h2>
<p><img src="https://czh-pic.oss-cn-guangzhou.aliyuncs.com/202302111205353.png" alt="vi"></p>
<h3 id="vimrc">vimrc</h3>
<ul>
<li><code>vimrc</code> 是 <code>vim</code> 的配置文件，可以设置 vim 的配置，包括：<strong>热键</strong>、<strong>配色</strong>、<strong>语法高亮</strong>、<strong>插件</strong> 等</li>
<li><code>Linux</code> 中 <code>vimrc</code> 有两个位置，<strong>家目录下的配置文件优先级更高</strong></li>
</ul>
<pre tabindex="0"><code>/etc/vim/vimrc
~/.vimrc
</code></pre><ul>
<li>常用的插件有：
<ul>
<li>代码补全</li>
<li>代码折叠</li>
<li>搜索</li>
<li>Git 集成</li>
<li>……</li>
</ul>
</li>
<li>网上有很多高手已经配置好的针对 <code>python</code> 开发的 <code>vimrc</code> 文件，可以下载过来直接使用，或者等大家多 <code>Linux</code> 比较熟悉后，再行学习！</li>
</ul>

    <h4><a href="https://czh-dev.gitee.io/czh-blog.gitee.io/">Back to Home</a></h4>
  </div>

  <div class="span3 bs-docs-sidebar" style="position:fixed;right: 40px;top: 50px;">
    <h1>catalogue</h1>
    <ul class="nav nav-list bs-docs-sidenav">
      <div class="toc-div">
        <nav id="TableOfContents">
  <ul>
    <li><a href="#目标">目标</a></li>
    <li><a href="#01-vi-简介">01. <code>vi</code> 简介</a>
      <ul>
        <li><a href="#11-学习-vi-的目的">1.1 学习 <code>vi</code> 的目的</a></li>
        <li><a href="#12-vi-和-vim">1.2 vi 和 vim</a></li>
      </ul>
    </li>
    <li><a href="#02-打开和新建文件">02. 打开和新建文件</a>
      <ul>
        <li><a href="#21-打开文件并且定位行">2.1 打开文件并且定位行</a></li>
        <li><a href="#22-异常处理">2.2 异常处理</a></li>
      </ul>
    </li>
    <li><a href="#03-三种工作模式">03. 三种工作模式</a>
      <ul>
        <li><a href="#末行模式命令">末行模式命令</a></li>
      </ul>
    </li>
    <li><a href="#04-常用命令">04. 常用命令</a>
      <ul>
        <li><a href="#命令线路图">命令线路图</a></li>
        <li><a href="#41-移动基本">4.1 移动（基本）</a></li>
        <li><a href="#42-移动程序">4.2 移动（程序）</a></li>
        <li><a href="#43-选中文本可视模式">4.3 选中文本（可视模式）</a></li>
        <li><a href="#44-撤销和恢复撤销">4.4 撤销和恢复撤销</a></li>
        <li><a href="#45-删除文本">4.5 删除文本</a></li>
        <li><a href="#46-复制粘贴">4.6 复制、粘贴</a></li>
        <li><a href="#47-替换">4.7 替换</a></li>
        <li><a href="#48-缩排和重复执行">4.8 缩排和重复执行</a></li>
        <li><a href="#49-查找">4.9 查找</a></li>
        <li><a href="#410-查找并替换">4.10 查找并替换</a></li>
        <li><a href="#411-插入命令">4.11 插入命令</a></li>
      </ul>
    </li>
    <li><a href="#05-分屏命令">05. 分屏命令</a>
      <ul>
        <li><a href="#51-末行命令扩展">5.1 末行命令扩展</a></li>
        <li><a href="#52-分屏命令">5.2 分屏命令</a></li>
      </ul>
    </li>
    <li><a href="#06-常用命令速查图">06. 常用命令速查图</a>
      <ul>
        <li><a href="#vimrc">vimrc</a></li>
      </ul>
    </li>
  </ul>
</nav>
      </div>
    </ul>
  </div>

</div>
<script src="https://cdn.jsdelivr.net/npm/gumshoejs@5.1.2/dist/gumshoe.min.js"></script>
<script>
  var spy = new Gumshoe('#TableOfContents a', {
    nested: true,
    nestedClass: 'active'
  });
</script>
<style>
   
  #TableOfContents li,
  #TableOfContents ul {
    list-style-type: none;
  }

  #TableOfContents ul {
    padding-left: 0px;
  }

  #TableOfContents li>a {
    display: block;
    padding: 4px 20px;
    font-size: 95%;
    color: #000000;
  }

  #TableOfContents li>a:hover,
  #TableOfContents li>a:focus {
    padding-left: 19px;
    color: #3A6bA5;
    text-decoration: none;
    background-color: transparent;
    border-left: 1px solid #3A6bA5;
  }

  #TableOfContents li.active>a,
  #TableOfContents li.active>a:hover,
  #TableOfContents li.active>a:focus {
    padding-left: 18px;
    font-weight: bold;
    color: #3A6bA5;
    background-color: transparent;
    border-left: 2px solid #3A6bA5;
  }

   
  #TableOfContents li>ul {
    padding-bottom: 10px;
  }

  #TableOfContents li li>a {
    padding-top: 1px;
    padding-bottom: 1px;
    padding-left: 30px;
    font-size: 14px;
    font-weight: normal;
  }

  #TableOfContents li li>a:hover,
  #TableOfContents li li>a:focus {
    padding-left: 29px;
  }

  #TableOfContents li li.active>a,
  #TableOfContents li li.active>a:hover,
  #TableOfContents li li.active>a:focus {
    padding-left: 28px;
    font-weight: 500;
  }

  #TableOfContents .nav-link.active+ul {
    display: block;
  }

  #TableOfContents li>ul {
    display: none;
  }

  #TableOfContents li.active>ul {
    display: inherit;
  }

  .toc-div {
    position: -webkit-sticky;
     
    position: sticky;
     
    top: 20px;
  }
</style>


        </div><footer class="container">
    <hr class="soften">
    <p>
    <a href="https://space.bilibili.com/1799809923">Love eating fried pork ribs</a> | 

&copy; 
<a href="http://jmf-portfolio.netlify.com" target="_blank">
    JM Fergeau
</a>
<span id="thisyear">2023</span>

    | My site


        | Built on <a href="//gohugo.io" target="_blank">Hugo</a>

</p>
    <p class="text-center">
        <a href="https://facebook.com">Facebook</a> 
        <a href="https://twitter.com">Twitter</a> 
        <a href="https://linkedin.com">Linkedin</a> 
        <a href="https://github.com">GitHub</a> 
        <a href="https://gitlab.com">GitLab</a>
    </p>
</footer>

</body><link rel="stylesheet" href="/czh-blog.gitee.io/css/bootstrap.css">
<link rel="stylesheet" href="/czh-blog.gitee.io/css/bootstrap-responsive.css">
<link rel="stylesheet" href="/czh-blog.gitee.io/css/style.css">

<script src="/czh-blog.gitee.io/js/jquery.js"></script>
<script src="/czh-blog.gitee.io/js/bootstrap-386.js"></script>
<script src="/czh-blog.gitee.io/js/bootstrap-transition.js"></script>
<script src="/czh-blog.gitee.io/js/bootstrap-alert.js"></script>
<script src="/czh-blog.gitee.io/js/bootstrap-modal.js"></script>
<script src="/czh-blog.gitee.io/js/bootstrap-dropdown.js"></script>
<script src="/czh-blog.gitee.io/js/bootstrap-scrollspy.js"></script>
<script src="/czh-blog.gitee.io/js/bootstrap-tab.js"></script>
<script src="/czh-blog.gitee.io/js/bootstrap-tooltip.js"></script>
<script src="/czh-blog.gitee.io/js/bootstrap-popover.js"></script>
<script src="/czh-blog.gitee.io/js/bootstrap-button.js"></script>
<script src="/czh-blog.gitee.io/js/bootstrap-collapse.js"></script>
<script src="/czh-blog.gitee.io/js/bootstrap-carousel.js"></script>
<script src="/czh-blog.gitee.io/js/bootstrap-typeahead.js"></script>
<script src="/czh-blog.gitee.io/js/bootstrap-affix.js"></script>
<script>
    _386 = { 
        fastLoad: false ,
        onePass: false , 
        speedFactor: 1 
    };

    
    function ThisYear() {
        document.getElementById('thisyear').innerHTML = new Date().getFullYear();
    };
</script>
</html>
